//#define __FORCE_TRACE__
//#define __FORCE_DEBUG__
//#define __FORCE_INFO__
#define THIS_FILE "tmf_core\main.sqf"
#include <tmf_constants.h>
#include <tmf_macros.h>

TRACE("Start");
waituntil {!isnil QUOTE(CFUNC(translate))};
TRACE("Functions Initialized");

QGVAR(mission_event_handler) addPublicVariableEventHandler {
	// We use the value of the variable as argument to the XNetRunEvent function.
	// _this contains ["VarName", VarValue]
	(_this select 1) call NFUNC(runevent);
};

GVAR(current_world) = toLower(getText (configFile>>"CfgWorlds">>worldName>> "worldname"));
GVAR(current_world_name) = "Stratis";
switch (GVAR(current_world)) do {
	default { //"\a3\map_stratis\stratis.wrp"
		GVAR(current_world_name) = "Stratis";
	};
};
DEBUG_1("Current World",[GVAR(current_world), GVAR(current_world_name)]);

CHK_STRING(GVAR(own_side),"WEST");
_side_players = GVAR(own_side);
_side_unit = "";
_sides = [];
if (X_MP) then {
	{
		_side_unit = str (side _x);
		if ((_sides find _side_unit) < 0) then {
			_sides set[count _sides, _side_unit];
		};
	} foreach playableUnits;
	if (count _sides == 1) then {
		_side_players = _sides select 0;
	};
} else {
	_side_players = str (side player);
};
GVAR(own_side) = _side_players;

GVAR(own_side) = switch(toupper(GVAR(own_side))) do {
			case "WEST":{"WEST"};
			case "EAST":{"EAST"};
			case "GUER":{"GUER"};
			case "RESISTANCE":{"GUER"};
			default{"WEST"};
};
GVAR(side_own) = switch(GVAR(own_side)) do {
			case "WEST":{west};
			case "EAST":{east};
			case "GUER":{resistance};
			default { west };
};
TRACE_1("Players Side", GVAR(own_side));

GVAR(enemy_side) = switch(toupper(GVAR(own_side))) do {
			case "WEST":{
				if ((west getFriend east) < 0.6) then {
					"EAST"
				} else {
					"GUER"
				};
			};
			case "EAST":{
				if ((east getFriend west) < 0.6) then {
					"WEST"
				} else {
					"GUER"
				};
			};
			case "GUER":{
				if ((resistance getFriend west) < 0.6) then {
					"WEST"
				} else {
					"EAST"
				};
			};
			default{"EAST"};
};
GVAR(side_enemy) = switch(GVAR(enemy_side)) do {
			case "WEST":{west};
			case "EAST":{east};
			case "GUER":{resistance};
			default { east };
};
TRACE_1("Enemy Side", GVAR(enemy_side));

GVAR(friendly_guerilla) = switch (GVAR(own_side)) do {
			case "WEST":{
				if ((west getFriend resistance) < 0.6) then {
					false
				} else {
					true
				};
			};
			case "EAST":{
				if ((east getFriend resistance) < 0.6) then {
					false
				} else {
					true
				};
			};
			default {
				true
			};
};

// Events common to both server and client
[0,QGVAR(all_object), {_this call FFUNC(registerObject);}] call NFUNC(addevent);
// Events common to both server and client
[0,QGVAR(all_var), {_this call FFUNC(setMissionVar);}] call NFUNC(addevent);
// create/update/delete a mission marker on all systems
[0,QGVAR(all_marker), {_this call FFUNC(updateMarker);}] call NFUNC(addevent);
// Executes an action triggered by a mission object on all systems
[0,QGVAR(all_action), {_this call FFUNC(executeObjectAction);}] call NFUNC(addevent);
// Creates/Updates a mission task on all systems
[0,QGVAR(all_task), {_this call FFUNC(updateTask);}] call NFUNC(addevent);
// Cleans all mission elements
[0,QGVAR(all_clean), {_this call FFUNC(cleanEvent);}] call NFUNC(addevent);
// Deletes ruins left by destroyed objects (radio tower, etc.)
[0,QGVAR(all_delruin), {_ruin = nearestObject [_this, "Ruins"];if (!isNull _ruin) then {deleteVehicle _ruin}}] call NFUNC(addevent);
// Launches the mission with the ID and parameters given
[0,QGVAR(all_start), {_this call FFUNC(launchMission);}] call NFUNC(addevent);
// Launches the mission with the ID and parameters given
[0,QGVAR(all_stop), {_this call FFUNC(stopMission);}] call NFUNC(addevent);
// Executes a mission function on all systems.
[0,QGVAR(all_execute), {_fnct = _this select 0; _params = _this select 1; call compile Format["%1 spawn %2",_params, _fnct];}] call NFUNC(addevent);
// Executes a mission function on all systems.
[0,QGVAR(all_message), {_this call CFUNC(handleMessage)}] call NFUNC(addevent);

["CURRENT_WORLD",GVAR(current_world)] call FFUNC(setFrameworkValue);

["USE_EXTERNAL_MISSIONS",tmf_use_external_missions] call FFUNC(setFrameworkValue);
["BASE_CONQUERED_TIMEOUT",tmf_conquered_base_timeout] call FFUNC(setFrameworkValue);

["MISSION_FRAMEWORK_PATH",TMF_PATH] call FFUNC(setFrameworkValue);
["MISSION_HEADER_FORMAT","m"] call FFUNC(setFrameworkValue);
["MISSION_CHAPTER_FORMAT","c"] call FFUNC(setFrameworkValue);
["STATIC_MISSIONS_COUNT",0] call FFUNC(setFrameworkValue);
["STATIC_MISSIONS_PATH",FORMAT["%1%2",TMF_PATH,"missions\"]] call FFUNC(setFrameworkValue);
["EXTERNAL_MISSIONS_COUNT",0] call FFUNC(setFrameworkValue);
["EXTERNAL_MISSIONS_PATH",FORMAT["%1%2","\tmf\","missions\"]] call FFUNC(setFrameworkValue);

["DEFAULT_EXPLOSIVES",["SatchelCharge_Remote_Ammo","DemoCharge_Remote_Ammo"]] call FFUNC(setFrameworkValue);
["DLG_WEATHER",[[localize "MSG_KW_RANDOM",-1,-1],[localize "MSG_KW_CLEAR",0,0.2],[localize "MSG_KW_CLOUDY",0,0.8],[localize "MSG_KW_LIGHTRAIN",0.3,0.7],[localize "MSG_KW_MEDIUMRAIN",0.5,0.7],[localize "MSG_KW_STORMY",0.8,1]]] call FFUNC(setFrameworkValue);
["DLG_POWER",[[localize "MSG_KW_RANDOM",-1,-1],[localize "MSG_KW_AUTOMATIC",0,0],[localize "MSG_KW_IMPROVED",1,0],[localize "MSG_KW_LEVELEDUP",2,0],[localize "MSG_KW_HEAVY",3,1],[localize "MSG_KW_NIGHTMARE",4,3]]] call FFUNC(setFrameworkValue);
["DLG_AIRSUPPORT",[[localize "MSG_KW_RANDOM",-1],[localize "MSG_KW_NONE",0],[localize "MSG_KW_FEW",0.3],[localize "MSG_KW_MEDIUM",0.6],[localize "MSG_KW_NORMAL",1],[localize "MSG_KW_INCREASED",1.6],[localize "MSG_KW_HEAVY",2],[localize "MSG_KW_UNBEARABLE",4]]] call FFUNC(setFrameworkValue);
["DLG_REINFORCEMENT",[[localize "MSG_KW_RANDOM",-1],[localize "MSG_KW_NONE",0],[localize "MSG_KW_RARE",1],[localize "MSG_KW_REGULAR",2],[localize "MSG_KW_FREQUENT",5],[localize "MSG_KW_TOAST",7]]] call FFUNC(setFrameworkValue);
["DLG_COMMUNICATION",[[localize "MSG_KW_RANDOM",-1],["100m",100],["200m",200],["300m",300],["400m",400],["500m",500],["600m",600],["700m",700],["800m",800],["900m",900]]] call FFUNC(setFrameworkValue);
["DLG_SNIPERS",[[localize "MSG_KW_RANDOM",-1,-1],[localize "MSG_KW_NONE",0,0],[localize "MSG_KW_RARE",0,1],[localize "MSG_KW_FEW",1,1],[localize "MSG_KW_SOME",1,3],[localize "MSG_KW_ALOT",2,4],[localize "MSG_KW_EVERYWHERE",5,8]]] call FFUNC(setFrameworkValue);
["DLG_CIVILIANS",[[localize "MSG_KW_NO",0,0],[localize "MSG_KW_YES",1,1]]] call FFUNC(setFrameworkValue);
["KRON_UPS_SHAREDIST",(If (isNil "KRON_UPS_sharedist") then {300} else {KRON_UPS_sharedist})] call FFUNC(setFrameworkValue);

["EMPTY_ARRAY",[]] call FFUNC(setFrameworkValue);

_mission_description = [];
SETVAL(_mission_description,TMF_MD_ID,0);
SETVAL(_mission_description,TMF_MD_NAME,missionName);
SETVAL(_mission_description,TMF_MD_DESC,localize "STR_MISSION_DESC");
SETVAL(_mission_description,TMF_MD_VERSION,"1.2");
[TMF_SERVER_INSTANCE_ID, "__MISSION_DESCRIPTION__",_mission_description] call FFUNC(setMissionVar);

[] call FFUNC(initCommon);

if (GVAR(SERVER)) then {
	// Stores all players related information
	GVAR(player_store) = "Land_HelipadEmpty_F" createVehicleLocal [0, 0, 0];
	// Stores all objects placed by the mission framework
	GVAR(placed_objs_store) = "Land_HelipadEmpty_F" createVehicleLocal [0, 0, 0];

	[1,QGVAR(s_execute), {diag_log format["server Execute %1",_this]; _fnct = {}; call compile Format["_fnct = %1;",(_this select 0)]; _params = _this select 1; _params spawn _fnct;}] call NFUNC(addevent);
	[1,QGVAR(s_log), {diag_log format _this}] call NFUNC(addevent);
	
	[] call FFUNC(initServer);
	
	[] spawn FFUNC(loadMissions);
};

if (GVAR(CLIENT)) then {
	[2,QGVAR(c_execute), {diag_log format["client Execute %1",_this]; _fnct = {}; call compile Format["_fnct = %1;",(_this select 0)]; _params = _this select 1; _params spawn _fnct;}] call NFUNC(addevent);

	player addEventHandler ["Respawn",{_this call FFUNC(initClient)}];
	[player,objNull] call FFUNC(initClient);
};
TRACE("End");
GVAR(initialized) = true;